<template>
    <el-form
      v-if="!!search"
      class="search is-hover-shadow"
      :model="searchModel"
      :label-width="search.labelWidth"
      :inline="true"
      label-position="left"
      :style="{ minHeight: showAll ? 'auto': '60px'}"
    >
      <el-form-item
        v-for="item in filterItems"
        :key="item.name"
        :label="item.label"
        :label-width="item.labelWidth"
        :prop="item.name"
      >
        <!-- select -->
        <el-select
          v-if="item.type === 'select'"
          v-model="searchModel[item.name]"
          :filterable="!!item.filterable"
          :multiple="!!item.multiple"
          size="small"
          clearable
          :placeholder="`请选择${item.label}`"
          :style="{ width: search.inputWidth, ...item.style }"
        >
          <el-option
            v-for="option of item.options"
            :key="option.value"
            :label="option.name"
            :value="option.value"
          ></el-option>
        </el-select>

        <!-- 单选 -->
        <el-radio-group
          v-model="searchModel[item.name]"
          v-else-if="item.type === 'radio'"
          :style="{ width: search.inputWidth, ...item.style }"
        >
          <el-radio
            v-for="option of item.options"
            :key="option.value"
            :label="option.value"
            >{{ option.name }}</el-radio
          >
        </el-radio-group>

        <!-- 单选按钮 -->
        <el-radio-group
          v-model="searchModel[item.name]"
          v-else-if="item.type === 'radio-button'"
          size="small"
          :style="{ width: search.inputWidth, ...item.style }"
        >
          <el-radio-button
            v-for="option of item.options"
            :key="option.value"
            :label="option.value"
            >{{ option.name }}</el-radio-button
          >
        </el-radio-group>

        <!-- 多选-->
        <el-checkbox-group
          v-model="searchModel[item.name]"
          v-else-if="item.type === 'checkbox'"
          :style="{ width: search.inputWidth, ...item.style }"
        >
          <el-checkbox
            v-for="option of item.options"
            :key="option.value"
            :label="option.value"
            >{{ option.name }}</el-checkbox
          >
        </el-checkbox-group>

        <!-- 多选按钮 -->
        <el-checkbox-group
          v-model="searchModel[item.name]"
          v-else-if="item.type === 'checkbox-button'"
          size="small"
          :style="{ width: search.inputWidth, ...item.style }"
        >
          <el-checkbox-button
            v-for="option of item.options"
            :key="option.value"
            :label="option.value"
            >{{ option.name }}</el-checkbox-button
          >
        </el-checkbox-group>

        <!-- 日期 年-月-日 -->
        <el-date-picker
          v-else-if="item.type === 'date'"
          v-model="searchModel[item.name]"
          type="date"
          format="YYYY-MM-DD"
          size="small"
          clearable
          @change="handleDateChange($event, item, 'YYYY-MM-DD')"
          :placeholder="`请选择${item.label}`"
          :style="{ width: search.inputWidth, ...item.style }"
        ></el-date-picker>

        <!-- 日期 年-月-日 时:分:秒-->
        <el-date-picker
          v-else-if="item.type === 'datetime'"
          v-model="searchModel[item.name]"
          type="datetime"
          size="small"
          clearable
          @change="handleDateChange($event, item, 'YYYY-MM-DD HH:mm:ss')"
          format="YYYY-MM-DD HH:mm:ss"
          :placeholder="`请选择${item.label}`"
          :style="{ width: search.inputWidth, ...item.style }"
        ></el-date-picker>

        <!-- 开始结束日期 年-月-日  -->
        <el-date-picker
          v-else-if="item.type === 'daterange'"
          v-model="searchModel[item.name]"
          type="daterange"
          format="YYYY-MM-DD"
          range-separator="至"
          start-placeholder="开始日期"
          end-placeholder="结束日期"
          size="small"
          clearable
          @change="handleRangeChange($event, item, 'YYYY-MM-DD')"
          :style="{ width: search.inputWidth || '250px', ...item.style }"
        ></el-date-picker>

        <!-- 开始结束日期 年-月-日 时:分:秒  -->
        <el-date-picker
          v-else-if="item.type === 'datetimerange'"
          v-model="searchModel[item.name]"
          type="datetimerange"
          format="YYYY-MM-DD HH:mm:ss"
          range-separator="至"
          start-placeholder="开始时间"
          end-placeholder="结束时间"
          size="small"
          clearable
          @change="handleRangeChange($event, item, 'YYYY-MM-DD HH:mm:ss')"
          :style="{ width: search.inputWidth || '340px', ...item.style }"
        ></el-date-picker>

        <!-- 数字输入框 -->
        <el-input-number
          v-else-if="item.type === 'number'"
          v-model="searchModel[item.name]"
          size="small"
          :placeholder="`请输入${item.label}`"
          controls-position="right"
          :min="item.min"
          :max="item.max"
          :style="{ width: search.inputWidth, ...item.style }"
        />

        <!-- 输入框 -->
        <el-input
          v-else
          v-model="searchModel[item.name]"
          size="small"
          clearable
          :placeholder="`请输入${item.label}`"
          :style="{ width: search.inputWidth, ...item.style }"
        ></el-input>
      </el-form-item>
      <el-form-item class="search-btn">
        <el-button icon="el-icon-search" size="small" style="background: #1890FF;color: #fff" @click="handleSearch">查询</el-button>
        <el-button icon="el-icon-refresh-right" size="small" @click="handleReset">重置</el-button>
        <el-button type="text" style="margin-left:10px" @click="closeSearch" v-if="filterItems.length >= searchShowLen">
          {{collapseText}}<i :class="showAll ? 'el-icon-caret-top': 'el-icon-caret-bottom'"></i>
        </el-button>
      </el-form-item>
    </el-form>
</template>

<script lang="ts">
import { defineComponent, reactive, ref, toRefs, computed } from 'vue'
import { formatDate } from '@/utils/util'

const getSearchModel = (search) => {
  const searchModel = {};
  if (search && search.fields) {
    search.fields.forEach((item) => {
      switch (item.type) {
        case "checkbox":
        case "checkbox-button":
          searchModel[item.name] = [];
          break;
        case "number":
          searchModel[item.name] = 0;
          break;
        default:
          searchModel[item.name] = null;
          break;
      }
      if (item.defaultValue !== undefined) {
        searchModel[item.name] = item.defaultValue;
        // 日期范围和时间范围真实变量默认值
        if (
          (item.type === "daterange" || item.type === "datetimerange") &&
          !!item.trueNames && Array.isArray(item.defaultValue)
        ) {
          item.defaultValue.forEach((val, index) => {
            searchModel[item.trueNames[index]] = val;
          });
        }
      }
    });
  }
  return searchModel;
};

export default defineComponent({
  name: 'FilterFrom',
  props: {
    // 搜索表单配置，false表示不显示搜索表单
    search: {
      type: [Boolean, Object],
      default: true,
    },
    searchShowLen: {
      type: Number,
      default: 3,
    }
  },
  emits: ['handle-search', 'handle-reset'],
  setup(props,{ emit }) {
    const state = reactive({
      searchModel: getSearchModel(props.search),
      showAll: false, //是否展开全部
      collapseText: computed(() => { 
        if(state.showAll) {
          return "收起"
        }else{
          return "展开"
        }
      }),
      filterItems: computed(()=> {
        if(typeof props.search == "object") {
          let fieldData: any[] = []
          fieldData = JSON.parse(JSON.stringify(props.search['fields']))
          if(state.showAll) {
            return fieldData
          }else{
            return fieldData.slice(0, props.searchShowLen)
          }
        }else{
          return props.search['fields']
        }
      })

    })

    // 条件查询
    const handleSearch = () => {
      emit('handle-search')
    }

    // 重置
    const handleReset = () => {
      if (JSON.stringify(state.searchModel) === "{}") {
        return;
      }
      state.searchModel = getSearchModel(props.search);
      emit('handle-reset')
    }

    // 查询条件过滤，
    const optimizeFields = (search) => {
      const searchModel = JSON.parse(JSON.stringify(state.searchModel));
      if (search && search.fields) {
        search.fields.forEach((item) => {
          if (!searchModel.hasOwnProperty(item.name)) {
            return;
          }
          // 如果搜索配置有远程搜索transform处理函数，执行transform
          if (!!item.transform) {
            searchModel[item.name] = item.transform(searchModel[item.name]);
          }
          // 删除日期范围默认的name字段
          if (
            (item.type === "daterange" || item.type === "datetimerange") &&
            !!item.trueNames
          ) {
            delete searchModel[item.name];
          }
          // 去除空字段
          if (item.type != "daterange" && item.type != "datetimerange" && !searchModel[item.name]) {
            delete searchModel[item.name]
          }
        });
      }
      return searchModel;
    };

    // 日期
    const handleDateChange = (date, item, format) => {
      state.searchModel[item.name] = !!date ? formatDate(date, format) : "";
    }
    // 日期范围
    const handleRangeChange = (date, item, format) => {
      const arr = !!date && date.map((d) => formatDate(d, format));
      state.searchModel[item.name] = !!arr ? arr : [];
      if (!item.trueNames) {
        return;
      }
      if (!!arr) {
        arr.forEach((val, index) => {
          state.searchModel[item.trueNames[index]] = val;
        });
      } else {
        item.trueNames.forEach((key) => {
          delete state.searchModel[key];
        });
      }
    }

    const closeSearch = () => {
      state.showAll = !state.showAll;
    }

    return {
      ...toRefs(state),
      optimizeFields,
      handleSearch,
      handleReset,
      handleDateChange,
      handleRangeChange,
      closeSearch,
    }
  }
})
</script>

<style lang="scss" scoped>
.search {
  padding: 20px 20px 0;
  border-radius: 3px;
  background: #f7f8fa;
  margin-bottom: 10px;
  display: flex;
  flex-wrap: wrap;
  transition: .3s;
  .el-form-item {
    margin-right: 20px;
    margin-bottom: 20px;
  }
  .search-btn {
    flex-shrink: 0;
    margin-left: auto;
  }
  :deep(.el-input-number .el-input__inner) {
    text-align: left;
  }
}
.is-hover-shadow:focus, .is-hover-shadow:hover{
  // box-shadow: 0 2px 12px 0 rgba(0,0,0,0.1);
  box-shadow: 0 2px 4px rgba(0,0,0,0.12),0 0 6px rgba(0,0,0,0.04);
}
</style>

